<?php
// +----------------------------------------------------------------------
// | 中联致远服务端框架
// +----------------------------------------------------------------------
// | Copyright (c) 2018 http://www.zhongliansoft.com All rights reserved.
// +----------------------------------------------------------------------
// | Author: tony <tanyu@zhongliansoft.com>
// +----------------------------------------------------------------------

namespace app\common\model;
use app\common\model\Config as ConfigsModel;
use app\common\model\BookApply as BookApplyModel;
use think\Validate;
use think\Db;
use think\facade\Log;

class BookBatchDraw extends Common
{
    //时间自动存储
    protected $autoWriteTimestamp = true;
    protected $updateTime = 'time';

    protected $rule = [
        'num'          => 'number',
    ];
    protected $msg = [
        'num'          => '数量必须为数字'
    ];

    /**
     * @param $post
     *
     * @return mixed
     * @throws \think\exception\DbException
     */
    public function tableData($post)
    {
        if(isset($post['limit'])){
            $limit = $post['limit'];
        }else{
            $limit = config('paginate.list_rows');
        }

        $tableWhere = $this->tableWhere($post);
        
        $list = $this->field('bbd.*, vs.season_name as season, vd.bmmc as dep, vsp.zymc as specialty, vc.plan_class_name as class, vdr.name as dir')
            ->alias('bbd')
            ->leftjoin('zl_view_get_seasons vs', 'vs.season_id = bbd.season')
            ->leftjoin('zl_view_get_depts vd', 'vd.bmdm = bbd.dep_id')
            ->leftjoin('zl_view_get_specicalties vsp', 'vsp.zydm = bbd.specialty_id and vsp.bmdm = bbd.dep_id ')
            ->leftjoin('zl_view_get_classes vc', 'vc.plan_class_id = bbd.class_id and vc.bmdm = bbd.dep_id and vc.zydm = bbd.specialty_id ')
            ->leftjoin('zl_view_get_dirs vdr', 'vdr.id = bbd.dir')
            ->where($tableWhere['where'])
            ->order($tableWhere['order'])
            ->paginate($limit);
        // $list = $this->field($tableWhere['field'])->where($tableWhere['where'])->order($tableWhere['order'])->paginate($limit);
        $data = $this->tableFormat($list->getCollection());         //返回的数据格式化，并渲染成table所需要的最终的显示数据类型

        $re['code'] = 0;
        $re['msg'] = '';
        $re['count'] = $list->total();
        $re['data'] = $data;
        return $re;
    }


    /**
     * 批量插入
     * @param $post
     * @return array
     */
    public function predrawSave($post)
    {
        $result = [
            'status' => false,
            'msg'    => '预发放失败',
            'data'   => []
        ];

        // 变量
        $new_id = $this->getMaxID();  // 最新ID
        $year = $post['year'];
        $season = $post['season'];
        $dep_id = $post['dep_id'];
        $specialty_id = $post['specialty_id'];
        $class_id = $post['class_id'];
        $dir = $post['dir'];
        $rate = $post['rate'] * 0.01;  // 百分比


        $condition1 = [];
        $condition2 = [];
        $condition1[] = ['year', 'eq', $year];
        $condition1[] = ['season', 'eq', $season];
        $condition1[] = ['dep_id', 'eq', $dep_id];

        $condition2[] = ['plan_year', 'eq', $year];
        $condition2[] = ['plan_season', 'eq', $season];
        $condition2[] = ['plan_dep_id', 'eq', $dep_id];
        $ConfigsModel = new ConfigsModel();
        $currYear = $ConfigsModel->getYear();  // 获取当前学年
        // $currSeason = $ConfigsModel->getSeason();  // 获取当前学年
        // if($currSeason == 1) {
        //     $currYear = $currYear - 1;
        // }

        $condition2[] = ['plan_grade', 'neq', $currYear];  // 不能是本学年的新生
        
        if(isset($specialty_id) && $specialty_id != ""){
            $condition1[] = ['specialty_id', 'eq', $specialty_id];
            $condition2[] = ['plan_specialty_id', 'eq', $specialty_id];
        }
        if(isset($class_id) && $class_id != ""){
            $condition1[] = ['class_id', 'eq', $class_id];
            $condition2[] = ['plan_class_id', 'eq', $class_id];
        }
        if(isset($dir) && $dir != ""){
            $condition1[] = ['dir', 'eq', $dir];
            $condition2[] = ['plan_dir', 'eq', $dir];
        }

        // 判断是否重复的预发放
        $info = $this->where($condition1)->count();
        if($info){
            $result['status'] = false;
            $result['msg'] = '所选条件下存在已预发放的班级、方向！';   
            return $result;
        }

        // 判断是否进行过批量发放
        $bookApplyModel = new BookApplyModel();
        $applyInfo = $bookApplyModel->where($condition1)->count();
        if($applyInfo){
            $result['status'] = false;
            $result['msg'] = '所选条件下存在已批量发放的班级、方向！';   
            return $result;
        }

        //根据年度、季度、部/院查询对应班级和计划人数
        $viewgetbookplanInfo = new ViewGetBookPlanInfo();
        $planInfo = $viewgetbookplanInfo->where($condition2)->select();
        if(!count($planInfo)){         
            $result['status'] = false;
            $result['msg'] = '所选条件下没有对应的老生预发放计划信息！';   
            return $result;
        }

        // 预发放数据
        $dataList = [];
        foreach($planInfo as $item) {
            $num = (float)round($rate * $item["plan_student"]);  // 计算数量（四舍五入）
            $dataList[] = array('id'=>$new_id, "year"=>$year, "season"=>$season, "dep_id"=>$dep_id, "num"=>$num,  
                                "specialty_id"=>$item["plan_specialty_id"], "class_id"=>$item["plan_class_id"], "dir"=>$item["plan_dir"]);
            $new_id++;
        }

        # 发放成功
        if($this->allowField(true)->saveAll($dataList, false))
        {
            $result['status'] = true;
            $result['msg']    = '预发放成功';
            return $result;
        }
        
        \think\facade\Request::token('__ZlServer_Token__', 'sha1');
        
        return $result;
    }


    // 教材预发放：根据ID获取明细
    public function getinfobyid($post)
    {
        $data = $this->field('bbd.*, vs.season_name as season, vd.bmmc as dep, vsp.zymc as specialty, vc.plan_class_name as class, vdr.name as dir')
                ->alias('bbd')
                ->leftjoin('zl_view_get_seasons vs', 'vs.season_id = bbd.season')
                ->leftjoin('zl_view_get_depts vd', 'vd.bmdm = bbd.dep_id')
                ->leftjoin('zl_view_get_specicalties vsp', 'vsp.zydm = bbd.specialty_id and vsp.bmdm = bbd.dep_id ')
                ->leftjoin('zl_view_get_classes vc', 'vc.plan_class_id = bbd.class_id and vc.bmdm = bbd.dep_id and vc.zydm = bbd.specialty_id ')
                ->leftjoin('zl_view_get_dirs vdr', 'vdr.id = bbd.dir')
                ->where('bbd.id',$post["id"])->find();
        return $data;
    }

    // 教材预发放：修改数量
    public function saveData($post)
    {
        $result = [
            'status' => true,
            'msg' => '保存成功',
            'data' => []
        ];
        
        // 数据校验
        $validate = new Validate($this->rule,$this->msg);
        if (!$validate->check($post)) {
            $result['status'] = false;
            $result['msg'] = $validate->getError();
            return $result;
        } 

        // 已经退书的不能再修改
        $sql = "select count(*) as count
        from zl_book_batch_draw bbd 
        left join zl_book_batch_draw bbd1 on bbd1.year = bbd.year and bbd1.season = bbd.season and bbd1.class_id = bbd.class_id and bbd1.dir = bbd.dir
        where bbd1.num < 0 and bbd.id = " . $post['id'];
        $info = Db::query($sql);
        if($info[0]["count"]){
            $result['status'] = false;
            $result['msg'] = '已经退书的不能再修改！';  
            return $result; 
        }
        
        // 关于已批量发放的判断
        $sql = "select count(*) as count
        from zl_book_apply ba 
        left join zl_book_batch_draw bbd on ba.year = bbd.year and ba.season = bbd.season and ba.class_id = bbd.class_id and ba.dir = bbd.dir
        where bbd.id = " . $post['id'];
        // where ba.is_ff = 1 and bbd.id = " . $post['id'];
        $info = Db::query($sql);
        if($info[0]["count"]){
            $result['status'] = false;
            $result['msg'] = '已经批量发放的不能再修改！';  
            return $result; 
        }

        // 关于已经签收的判断
        $sql = "select count(*) as count
        from zl_book_draw bd 
        left join zl_book_batch_draw bbd on bd.draw_year = bbd.year and bd.draw_season = bbd.season and bd.draw_class_id = bbd.class_id and bd.draw_dir = bbd.dir
        where bbd.id = " . $post['id'];
        $info = Db::query($sql);

        $plan_num = $this->getNumByID($post['id']);  // 计划数量
        $yqs_num = $info[0]["count"];  # 已签收数量
        
        if($yqs_num < $plan_num)  # 已签收数量小于计划数量
        {
            // if ($post['num'] > $plan_num)
            // {
            //     $result['status'] = false;
            //     $result['msg'] = '预发放数量不能大于计划数量！';
            //     return $result;
            // }
            // else 
            if ($post['num'] < $yqs_num)
            {
                $result['status'] = false;
                $result['msg'] = '预发放数量不能小于已签收数量('.$yqs_num.')！';
                return $result;
            }
        }
        else{
            if($post['num'] != $yqs_num){
                $result['status'] = false;
                $result['msg'] = '预发放数量必须等于已签收数量('.$yqs_num.')！';  
                return $result; 
            } 
        }
        
        // 保存（只修改过数量）
        if (!$this->allowField(true)->save(["num"=>$post["num"]], ['id'=>$post['id']]))
        {
            $result['status'] = false;
            $result['msg'] = '保存失败';
            return $result; 
        }
        
        \think\facade\Request::token('__ZlServer_Token__', 'sha1');
        //$result['token'] = \think\facade\Request::token('__ZlServer_Token__', 'sha1');
         
        return $result;
    }

    // 退书
    public function predrawReturn($post)
    {
        $result = [
            'status' => false,
            'msg'    => '退书失败',
            'data'   => []
        ];

        // 判断是否存在预发放信息
        $condition = [];  # 必须是二维数组
        $condition[] = ['year', 'eq', $post['return_year']];
        $condition[] = ['season', 'eq', $post['return_season']];
        $condition[] = ['class_id', 'eq', $post['return_class_id']];
        $condition[] = ['dir', 'eq', $post['dir']];
        $condition[] = ["num", "gt", 0];
        $total_num = $this->where($condition)->value("num");  # 总数
        if($total_num == NULL){
            $result['status'] = false;
            $result['msg'] = '该年度、季度、班级、方向下，不存在预发放信息！';  
            return $result; 
        } 
        
        $data_id = $this->where($condition)->value("id");  # 总数
        // 关于已批量发放的判断
        $sql = "select count(*) as count
        from zl_book_apply ba 
        left join zl_book_batch_draw bbd on ba.year = bbd.year and ba.season = bbd.season and ba.class_id = bbd.class_id and ba.dir = bbd.dir
        where bbd.id = " . $data_id;

        // where ba.is_ff = 1 and bbd.id = " . $post['id'];
        $info = Db::query($sql);
        if($info[0]["count"]){
            $result['status'] = false;
            $result['msg'] = '已经批量发放的不能再修改！';  
            return $result; 
        }
        
        if($post["num"] > $total_num){
            $result['status'] = false;
            $result['msg'] = '退书数量不能大于预发放数量！';  
            return $result; 
        }

        // 判断是否存在重复的数据
        array_pop($condition);  # 移除最后一个元素;
        $condition[] = ["num", "lt", 0];
        $info = $this->where($condition)->count();
        if($info){
            $result['status'] = false;
            $result['msg'] = '同一年度、季度、班级、方向只能退书一次！';  
            return $result; 
        } 
        
        // 退书数量不能超出未签收数量 = 预发放数量 - 退书数量(0) - 已签收数量
        // 因为不能重复退书，所以退书数量必为0
        $qs_num = $this->getQSNum($post);  # 获取已签收数量
        if($post["num"] > $total_num - $qs_num){
            $result['status'] = false;
            $result['msg'] = '退书数量不能大于未签收数量！';  
            return $result;
        }

        $new_id = $this->getMaxID();
        $data = array('id'=>$new_id, "year"=>$post["return_year"], "season"=>$post["return_season"], 
                      "num"=>$post["num"] * -1, "dep_id"=>$post["return_dep_id"], "specialty_id"=>$post["return_specialty_id"], 
                      "class_id"=>$post["return_class_id"], "dir"=>$post["dir"], "return_reason"=>$post["return_reason"]);
            
        // 退书成功
        if($this->allowField(true)->save($data))
        {
            $result['status'] = true;
            $result['data'] = $this->tablereturnData(['id'=>$new_id]);
            $result['msg']    = '退书成功';
        }

        
        \think\facade\Request::token('__ZlServer_Token__', 'sha1');
        return $result;
    }


    // where搜索条件（预发放）
    protected function tableWhere($post)
    {
        $where = [];
        if(isset($post['year']) && $post['year'] != ""){
            $where[] = ['year', 'eq', $post['year']];
        }
        if(isset($post['season']) && $post['season'] != ""){
            $where[] = ['season', 'eq', $post['season']];
        }
        if(isset($post['dep_id']) && $post['dep_id'] != ""){
            $where[] = ['dep_id', 'eq', $post['dep_id']];
        }
        if(isset($post['specialty_id']) && $post['specialty_id'] != ""){
            $where[] = ['specialty_id', 'eq', $post['specialty_id']];
        }
        if(isset($post['class_id']) && $post['class_id'] != ""){
            $where[] = ['class_id', 'eq', $post['class_id']];
        }
        if(isset($post['dir']) && $post['dir'] != ""){
            $where[] = ['dir', 'eq', $post['dir']];
        }
        if(isset($post['is_dy']) && $post['is_dy'] != ""){
            $where[] = ['is_dy', 'eq', $post['is_dy']];
        }
        
        $where[] = ["num", "gt", 0];  # 数量为正数
        $result['where'] = $where;
        $result['field'] = "*";
        $result['order'] = ['bbd.year', 'bbd.season', 'bbd.dep_id', 'bbd.specialty_id', 'bbd.class_id', 'bbd.dir', 'bbd.id ASC'];
        return $result;
    }


    /**
     * @param $post（退书）
     *
     * @return mixed
     * @throws \think\exception\DbException
     */
    public function tablereturnData($post)
    {
        if(isset($post['limit'])){
            $limit = $post['limit'];
        }else{
            $limit = config('paginate.list_rows');
        }

        $tableWhere = $this->tablereturnWhere($post);
        $list = $this->field('bbd.*, vs.season_name as season, vd.bmmc as dep, vsp.zymc as specialty, vc.plan_class_name as class, vdr.name as dir')
            ->alias('bbd')
            ->leftjoin('zl_view_get_seasons vs', 'vs.season_id = bbd.season')
            ->leftjoin('zl_view_get_depts vd', 'vd.bmdm = bbd.dep_id')
            ->leftjoin('zl_view_get_specicalties vsp', 'vsp.zydm = bbd.specialty_id and vsp.bmdm = bbd.dep_id ')
            ->leftjoin('zl_view_get_classes vc', 'vc.plan_class_id = bbd.class_id and vc.bmdm = bbd.dep_id and vc.zydm = bbd.specialty_id ')
            ->leftjoin('zl_view_get_dirs vdr', 'vdr.id = bbd.dir')
            ->where($tableWhere['where'])
            ->order($tableWhere['order'])
            ->paginate($limit);
        // $list = $this->field($tableWhere['field'])->where($tableWhere['where'])->order($tableWhere['order'])->paginate($limit);
        $data = $this->tablereturnFormat($list->getCollection());         //返回的数据格式化，并渲染成table所需要的最终的显示数据类型

        $re['code'] = 0;
        $re['msg'] = '';
        $re['count'] = $list->total();
        $re['data'] = $data;
        return $re;        //返回的数据格式化，并渲染成table所需要的最终的显示数据类型
    }


    // where搜索条件（退书）
    public function tablereturnWhere($post)
    {
        $where = [];
        if(isset($post['year']) && $post['year'] != ""){
            $where[] = ['year', 'eq', $post['year']];
        }
        if(isset($post['season']) && $post['season'] != ""){
            $where[] = ['season', 'eq', $post['season']];
        }
        if(isset($post['dep_id']) && $post['dep_id'] != ""){
            $where[] = ['dep_id', 'eq', $post['dep_id']];
        }
        if(isset($post['specialty_id']) && $post['specialty_id'] != ""){
            $where[] = ['specialty_id', 'eq', $post['specialty_id']];
        }
        if(isset($post['class_id']) && $post['class_id'] != ""){
            $where[] = ['class_id', 'eq', $post['class_id']];
        }
        if(isset($post['dir']) && $post['dir'] != ""){
            $where[] = ['dir', 'eq', $post['dir']];
        }
        if(isset($post['id']) && $post['id'] != ""){
            $where[] = ['bbd.id', 'eq', $post['id']];
        }
        // if(isset($post['return_reason']) && $post['return_reason'] != ""){
        //     $where[] = ['return_reason', 'like', '%'.$post['return_reason'].'%'];
        // }
        $where[] = ["num", "lt", 0];  # 数量为负数
        $result['where'] = $where;
        $result['field'] = "*";
        $result['order'] = ['id ASC'];
        return $result;
    }


    /**
     * @param $list
     *
     * @return mixed
     */
    public function tableFormat($list)
    {
        foreach($list as &$val){
            $val['time'] = getTime($val['time']); 
            // $val['season'] = getSeason($val['season']);
            // $val['dir'] = getDir($val['dir']);
        }
        return $list;
    }

    /*
     */
    public function tablereturnFormat($list)
    {
        foreach($list as &$val){
            $val['time'] = getTime($val['time']); 
            // $val['season'] = getSeason($val['season']);
            // $val['dir'] = getDir($val['dir']);
            $val['num'] = abs($val['num']);
        }
        return $list;
    }

    // 根据ID获取计划数量
    public function getNumByID($id)
    {
        $num = $this->field('vbp.plan_student')
                ->alias('bbd')
                ->leftjoin('zl_view_get_book_plan_info vbp', 'vbp.plan_dep_id = bbd.dep_id and vbp.plan_specialty_id = bbd.specialty_id and vbp.plan_class_id = bbd.class_id')
                ->where('bbd.id', $id)->value("vbp.plan_student");
        return $num;
    }


    // 获取最新的id
    public function getMaxID()
    {
        $pre_id = date("Ymd");  # 编号前缀
        $condition = [['id', "like",  $pre_id."%"]];  # 必须是二维数组
        $res = $this->where($condition)->max('id');
        if($res){
			$num = (int)substr($res, -4);  # 截取最后4位
            $num++;
			$res = $pre_id.sprintf("%04d", $num);  # 补足4位
        }
        else{
            $res = $pre_id."0001";
        }
        return $res;
    }


    // 获取已签收的数量
    public function getQSNum($post)
    {
        $condition = [];
        $condition[] = ['draw_year', 'eq', $post['return_year']];
        $condition[] = ['draw_season', 'eq', $post['return_season']];
        $condition[] = ['draw_class_id', 'eq', $post['return_class_id']];
        $condition[] = ['draw_dir', 'eq', $post['dir']];

        $bookdrawModel = new BookDraw();
        $qs_num = $bookdrawModel->where($condition)->count();
        return $qs_num;
    }

    
    // 教材预发放：重置打印状态 1->0
    public function bookpreresetprintstatus($data)
    {
        $result = [
            'status' => false,
            'msg'    => '重置失败',
            'data'   => [],
        ];

        $ids_arr = explode(",", $data['ids']);
        $dataList = [];
        foreach($ids_arr as $val) {
            $dataList[] = array('id'=>$val, "is_dy"=>"0");
        }
        # 重置成功
        if($this->isUpdate(true)->saveAll($dataList))
        {
            $result['status'] = true;
            $result['msg']    = '重置成功';
        }
        return $result;
    }

       
    // 教材预发放：打印状态改变 0->1
    public function bookpreprintstatus($data)
    {
        $result = [
            'status' => false,
            'msg'    => '打印失败',
            'data'   => [],
        ];

        $ids_arr = explode(",", $data['ids']);
        $dataList = [];
        foreach($ids_arr as $val) {
            $dataList[] = array('id'=>$val, "is_dy"=>"1");
        }
        # 打印成功
        if($this->isUpdate(true)->saveAll($dataList))
        {
            $result['status'] = true;
            $result['msg']    = '打印成功';
        }
        return $result;
    }
}